fix(bitgo): ship npm-shrinkwrap.json for npm consumers#9213
fix(bitgo): ship npm-shrinkwrap.json for npm consumers#9213mihir-bitgo wants to merge 2 commits into
Conversation
4d56e22 to
790cf76
Compare
ReviewOverviewAdds a 🔴 Critical — sibling version resolution at pack time
The canary plan won't surface this — a standalone 🟠 Significant
🟡 Minor / style
Test coverageNo automated test (reasonable for release tooling), but given the sibling-timing risk, the unchecked canary/dry-run boxes should be treated as merge blockers. Bottom lineRight mechanism, but the pack-time sibling resolution against the public registry is a real correctness/reliability hazard for a coordinated monorepo release, and the Generated by Claude Code |
npm `overrides` only pins versions when bitgo is the root of an `npm install`; consumers installing bitgo as a dependency still resolve unpinned transitive versions. Ship npm-shrinkwrap.json inside the published package so those installs are pinned too. Wired as bitgo's `prepack` script (not a separate release-pipeline step) so it always runs after lerna bumps the version on disk but before the tarball is packed, keeping the shrinkwrap's top-level version in sync with whatever actually gets published. Generation happens in an isolated temp copy since `npm shrinkwrap` isn't workspace-aware and modules/bitgo/.npmrc disables package-lock. `@bitgo/*` siblings are excluded from resolution: `lerna publish` bumps and packs every package in the same operation, so a sibling's new version isn't guaranteed to be live on the registry yet when bitgo is packed — resolving it here would fail the release or pin a stale version. Consumers resolve `@bitgo/*` siblings normally at install time instead; the shrinkwrap still pins whatever those siblings pull in transitively. Generation only runs when BITGO_GENERATE_SHRINKWRAP=true (set by the release workflow), so a plain local `npm pack` doesn't force a network install of the full dependency tree. TICKET: WCN-604
npm only honors a shipped npm-shrinkwrap.json for consumers when the registry's own metadata reports hasShrinkwrap: true — this was never confirmed against a real npm publish (only Verdaccio, which didn't set it). Add a post-publish check so a silent registry-side omission fails the release instead of shipping a bitgo package whose shrinkwrap consumers silently don't get. Set BITGO_GENERATE_SHRINKWRAP=true on the publish steps so bitgo's prepack script actually runs during release. Retry the registry check with the job's existing `retry` binary since dist metadata can lag briefly right after publish. TICKET: WCN-604
790cf76 to
23ec271
Compare
|
Thanks for the review — the critical finding is correct and I hadn't accounted for the sibling-publish race. Fixed:
Agreed the canary-only validation was insufficient for the sibling-timing hazard specifically — that risk is now structurally eliminated rather than something to catch in testing. Canary/dry-run validation of the |
|
Claude finished @mihir-bitgo's task —— View job Code Review Complete
Review SummaryThis PR effectively addresses the critical sibling resolution race condition identified by Otto while implementing a sound mechanism for shipping ✅ Key StrengthsSibling Resolution Race FixThe implementation correctly addresses Otto's critical concern by:
Environment Gating
Registry Verification
Clean Implementation
🟡 Minor ObservationsCode Style
Dependencies
Package.json Changes
🔍 Edge Cases Handled
Recommendation✅ Approve - The implementation correctly solves the stated problem while addressing all critical concerns from the initial review. The sibling resolution race condition is structurally eliminated, network access is properly gated, and the registry verification includes appropriate retry logic. The canary validation mentioned in the PR description remains the only outstanding item, but the code changes themselves are sound and ready for merge pending that validation. Job run: https://github.com/BitGo/BitGoJS/actions/runs/... |
Summary
overrides(fix(root): add npm overrides mirroring yarn resolutions #9212) only pins versions whenbitgois the root of annpm install; consumers installingbitgoas a dependency still resolve unpinned transitive versionsprepackscript onmodules/bitgo(scripts/generate-bitgo-shrinkwrap.ts) that generatesnpm-shrinkwrap.jsonin an isolated temp copy (outside the workspace, sincenpm shrinkwrapisn't workspace-aware andmodules/bitgo/.npmrcdisablespackage-lock) and ships it in the published tarballprepackinstead of a separate release-pipeline step means it fires after lerna bumps the version on disk but before packing, so the shrinkwrap's top-level version always matches what's actually publishedhasShrinkwrapmetadata isn'ttrue— this was never confirmed on a real npm publish per the ticket (Verdaccio didn't set it)Test plan
.github/workflows/npmjs-release.yml,modules/bitgo/package.json) parse/lint cleanlybitgo@0.0.0-canary.Nfrom a temp copy including a generated shrinkwrap and confirmnpm view bitgo@<canary> dist.hasShrinkwrapistruenpm auditis cleanDepends on #9212 (root
overrides) merging first so the generated shrinkwrap reflects the pinned tree.TICKET: WCN-604
🤖 Generated with Claude Code